package com.acme.bankapp.domain.bank;

import com.acme.bankapp.domain.exception.*;

/**
 * Class provides checking accounts functionality with overdraft
 * @author alex
 */
@SuppressWarnings("serial")
public class CheckingAccount extends AbstractAccount {
	private double overdraft;
	
	/**
	 * @param balance the balance
	 * @param overdraft the overdraft
	 */
	public CheckingAccount(double balance, double overdraft) {
		if ((balance >= - overdraft) && (overdraft > 0)) {
			this.balance = balance;
			this.overdraft = overdraft;
		} else {
			throw new IllegalArgumentException();
		}
	}
	
	/**
	 * @param x the money
	 * @throws OverDraftLimitExceededException 
	 */
	public void withdraw(double x) throws OverDraftLimitExceededException {
		if (this.balance + this.overdraft >= x) {
			this.balance -= x;
		} else {
			throw new OverDraftLimitExceededException(this);
		}
	}
	
	/**
	 * @return the maximum amount to withdraw
	 */
	public double maximumAmountToWithdraw() {
		return (this.balance + this.overdraft);
	}
	
	/**
	 * @return the sting presentation
	 */
	public String toString() {
		return "Checking account #" + this.accountId + ", balance: " + this.balance + ", overdraft: " + this.overdraft;
	}
	
	/**
	 * @return the checking account object hash code
	 */
	@Override
	public int hashCode() {
		final int prime = 31;
		int result = 1;
		result = prime * result + accountId;
		return result;
	}
	
	/**
	 * @param obj the checking account
	 * @return whether checking accounts are equal
	 */
	@Override
	public boolean equals(Object obj) {
		if (this == obj)
			return true;
		if (obj == null)
			return false;
		if (getClass() != obj.getClass())
			return false;
		CheckingAccount other = (CheckingAccount) obj;
		if (accountId != other.accountId)
			return false;
		return true;
	}
}
